MySQLとRDS MySQLとRDS Auroraのキャッシュウォーミング機能を調べた
データベースのキャッシュウォームアップについて
キャッシュを活用して高速にクエリーをさばいているDBシステムも、リスタートなどのタイミングでキャッシュが失われると、途端に処理性能が著しく低下します。 そのようなケースに備えて、有名なDBシステムではスタート時にダンプ済みキャッシュを読み込んでウォームアップする機能が提供されています。
今回は以下の MySQL 系データベースについてキャッシュウォーミング機能を確認しました。
- MySQL 5.6
- RDS MySQL 5.6
- MySQL 5.7
- RDS Aurora
それでは順に見ていきましょう。
MySQL 5.6
InnoDB で MySQL を使っている場合、クエリーキャッシュは buffer pool に保存されます。 buffer pool はメモリー上にあるため、MySQL を一旦停止すると失われてしまいます。
この問題を解決するために buffer pool をファイルシステムに入出力する機能が MySQL 5.6.3 から導入されました。
ファイルに出力する
即時出力するためには
mysql > SET GLOBAL innodb_buffer_pool_dump_now= ON;
正常終了時に出力するためには
mysql > SET GLOBAL innodb_buffer_pool_dump_at_shutdown=ON;
常にこの設定を有効にするのであれば my.cnf で
[mysqld] innodb_buffer_pool_dump_at_shutdown=ON
とします。
MySQL が異常終了し、buffer pool が書き出されないケースに備えて innodb_buffer_pool_dump_now を定期的に呼び出すとシステムはより堅牢になります。
ファイルから読み込む
即時に読み込むには
mysql > SET GLOBAL innodb_buffer_pool_load_now=ON;
即時読み込みをキャンセルするには
mysql > SET GLOBAL innodb_buffer_pool_load_abort=ON;
起動時に読み込むには my.cnf で
[mysqld] innodb_buffer_pool_load_at_startup=ON
とします。
RDS for MySQL 5.6
RDS for MySQL では 5.6.19 から Innodb の Cache Warming に対応しました。
機能発表時に弊社ブログでも解説しております。
https://dev.classmethod.jp/cloud/aws/rds-for-mysql-cache-warming/
以下では 5.6.19 以上のバージョンを前提とします。
RDS はファイルシステムの操作が制限されているため、通常の MySQL と同様の手順で実行しても、次のような権限周りのエラーが発生します。
mysql> SET GLOBAL innodb_buffer_pool_load_abort=ON; ERROR 1227 (42000): Access denied; you need (at least one of) the SUPER privilege(s) for this operation
そのため
- パラメーターグループ
- ストアドプロシージャ
で制御します。
パラメーターグループで制御するもの
- innodb_buffer_pool_dump_at_shutdown
- innodb_buffer_pool_load_at_startup
についてはパラメーターグループで制御します。 デフォルトではともに OFF(=0) となっています。
ストアドプロシージャで制御するもの
即時実行する
- innodb_buffer_pool_dump_now
- innodb_buffer_pool_load_now
- innodb_buffer_pool_load_abort
は rds_ が接頭するストアドプロシージャ経由で実行します。 具体的には
mysql > CALL mysql.rds_innodb_buffer_pool_dump_now(); mysql > CALL mysql.rds_innodb_buffer_pool_load_now(); mysql > CALL mysql.rds_innodb_buffer_pool_load_abort();
というようになります。
MySQL 5.7
MySQL 5.7.2 と 5.7.7 で Cache Warming 周りの機能追加が行われました。 以下ではより新しい 5.7.7 以降を前提とします。
- innodb_buffer_pool_dump_at_shutdown
- innodb_buffer_pool_load_at_startup
はともにデフォルトで ON となり、buffer pool が MySQL の終了・停止で引き継がれるようになりました。
また、新規グローバル変数 innodb_buffer_pool_dump_pct が追加され、ダンプする buffer pool の割合を指定できるようになりました。 デフォルトは 25 となっており、キャッシュが乗っかっているページの新ものから 25% 分がダンプされます。
割合を変更するには
mysql > SET GLOBAL innodb_buffer_dump_pct=40;
常にこの設定にするのであれば my.cnf で
[mysqld] innodb_buffer_dump_pct=40
とします。
RDS Aurora
"Survivable" Cache Warming
Aurora ではキャッシュ管理は別プロセスになっており、独自のの機構でクエリーキャッシュやDBシステムリスタート時の Cache Warming を実現しているそうです。 (Aurora 系ドキュメントでは "Survivable" Cache Warming と形容されています)
この "Survivable" Cache Warming をコントロールするパラメーターグループを探したのですが、見つけられませんでした。 ご存じの方は教えて下さい。
キャッシュヒットに関する CloudWatch メトリクス
BufferCacheHitRatio : The percentage of requests that are served by the Buffer cache. ResultsetCacheHitRatio : The percentage of requests that are served by the Resultset cache.
という Aurora 固有のクエリーキャッシュ系メトリクスが追加されています。
innoDB のキャッシュ系パラメーターの扱い
パラメーターグループには InnoDB 向けの
- innodb_buffer_pool_dump_at_shutdown
- innodb_buffer_pool_load_at_startup
が残っていますが、これらが OFF(=0) のままDBをリスタートしても、SELECT でキャッシュヒットすることが確認できました。 (メトリクス BufferCacheHitRatio の値から類推)
その他
特定のデータベースに依存しないウォームアップとしては、起動直後に SQL を流すアプローチがよく知られています。
参考
MySQL 5.6
MySQL 5.6 RDS
- https://dev.classmethod.jp/cloud/aws/rds-for-mysql-cache-warming/
- https://aws.amazon.com/blogs/aws/rds-mysql-cache-warming/
- http://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/CHAP_MySQL.html#MySQL.Concepts.InnoDBCacheWarming
- http://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/mysql_rds_innodb_buffer_pool_dump_now.html
MySQL 5.7
- http://dev.mysql.com/doc/refman/5.7/en/innodb-preload-buffer-pool.html
- http://dev.mysql.com/doc/refman/5.7/en/innodb-parameters.html#sysvar_innodb_buffer_pool_dump_pct
- http://tech.gmo-media.jp/post/128523146249/innodb-buffer-pool-load-at-startup